@file:OptIn(ExperimentalLayoutApi::class)

package com.ohuang.wallpapermanager.screen


import android.net.Uri
import androidx.activity.compose.BackHandler
import androidx.activity.compose.rememberLauncherForActivityResult
import androidx.compose.animation.AnimatedVisibility
import androidx.compose.foundation.Image
import androidx.compose.foundation.border
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.ExperimentalLayoutApi
import androidx.compose.foundation.layout.FlowRow
import androidx.compose.foundation.layout.Row

import androidx.compose.foundation.layout.Spacer

import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.heightIn
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.rememberScrollState
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.foundation.text.KeyboardOptions
import androidx.compose.foundation.verticalScroll
import androidx.compose.material3.Button
import androidx.compose.material3.CircularProgressIndicator
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.Text
import androidx.compose.material3.TextField
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.MutableState
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.input.KeyboardType
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import com.ohuang.wallpapermanager.compose.TipDialog
import com.ohuang.wallpapermanager.compose.clickableSafe
import com.ohuang.wallpapermanager.compose.dp2sp
import com.ohuang.wallpapermanager.compose.onClickSafe
import com.ohuang.wallpapermanager.compose.rememberFilePainter
import com.ohuang.wallpapermanager.compose.rememberFilePainterSafe
import com.ohuang.wallpapermanager.compose.rememberUriPainter
import com.ohuang.wallpapermanager.compose.rememberUriPainterSafe
import com.ohuang.wallpapermanager.compose.tryCatch
import com.ohuang.wallpapermanager.compose.update
import com.ohuang.wallpapermanager.ui.theme.colorMain
import com.ohuang.wallpapermanager.vm.EditWallPaperInfoViewModel
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.launch

sealed class EditWallPaperInfoScreenEvent {
    object Save : EditWallPaperInfoScreenEvent()
    object Delete : EditWallPaperInfoScreenEvent()
    class ImgChange(val uri: String) : EditWallPaperInfoScreenEvent()
}


@Composable
fun EditWallPaperInfoScreen(
    isLockWall: Boolean,
    id: Long,
    goBack: () -> Unit,
    viewModel: EditWallPaperInfoViewModel = androidx.lifecycle.viewmodel.compose.viewModel()
) {

    val showBackDialog = remember {
        mutableStateOf(false)
    }
    LaunchedEffect(key1 = id, key2 = isLockWall, block = {
        viewModel.init(isLockWall, id)
    })
    val rememberCoroutineScope = rememberCoroutineScope() // 放前面 避免后面组件退出重组时，导致协程结束
    BackHandler {
        showBackDialog.value = true
    }
    val isLoading = viewModel.editWallPaperInfoState.value.isLoading
    if (isLoading) {
        Loading()
        return
    }

    if (showBackDialog.value) {
        TipDialog(title = "", content = "数据还没保存,是否退出?", confirmClick = {
            showBackDialog.value = false
            goBack()
        }, onDismissRequest = {
            showBackDialog.value = false
        })
    }


    AnimatedVisibility(visible = !isLoading) {
        Column() {
            TopBar(
                title = "${if (id == 0L) "新建" else "编辑"}${if (isLockWall) "锁屏" else "桌面"}壁纸",
                backClick = {
                    showBackDialog.value = true
                }
            )


            EditWallPaperInfoScreenImpl(
                state = viewModel.editWallPaperInfoState.value
            ) {
                dispatchEvent(it, rememberCoroutineScope, viewModel, goBack)
            }
        }
    }

}

@Composable
private fun Loading() {
    Box(modifier = Modifier.fillMaxSize()) {
        Column(
            modifier = Modifier.align(Alignment.Center),
            verticalArrangement = Arrangement.Center,
            horizontalAlignment = Alignment.CenterHorizontally
        ) {
            CircularProgressIndicator()
            Text("加载中...", modifier = Modifier.padding(top = 20.dp))
        }
    }
}

private fun dispatchEvent(
    it: EditWallPaperInfoScreenEvent,
    rememberCoroutineScope: CoroutineScope,
    viewModel: EditWallPaperInfoViewModel,
    goBack: () -> Unit,
) {
    when (it) {
        is EditWallPaperInfoScreenEvent.Save -> {
            rememberCoroutineScope.launch {
                viewModel.saveWallPaperInfo()
                goBack()
            }
        }

        is EditWallPaperInfoScreenEvent.Delete -> {
            rememberCoroutineScope.launch {
                viewModel.deleteWallPaperInfo()
                goBack()
            }
        }

        is EditWallPaperInfoScreenEvent.ImgChange -> {
            viewModel.updateUri(it.uri)
        }
    }
}

@Preview(backgroundColor = 0xffffffff, showBackground = true)
@Composable
fun EditWallPaperInfoScreenShow() {
    EditWallPaperInfoScreenImpl(EditWallPaperInfoState())
}

@Composable
private fun EditWallPaperInfoScreenImpl(
    state: EditWallPaperInfoState,
    onEvent: (EditWallPaperInfoScreenEvent) -> Unit = {}
) {
    Column(
        modifier = Modifier
            .fillMaxSize()
            .verticalScroll(rememberScrollState())
    ) {
        ImageShow(uri = state.uri, filePath = state.filePath, uriCall = {
            onEvent(EditWallPaperInfoScreenEvent.ImgChange(it))
        })
        ForceShowSelectBox(state.isForceShow)
        SelectWeekBox(state.timeRule.week)
        SelectTimeBox(state.timeRule.timeFrame)
        SubmitButton(
            isVisible = state.uri.isNotEmpty() || state.filePath.isNotEmpty(),
            isShowDelete = state.id != 0L,
            onEvent = onEvent
        )
        Spacer(modifier = Modifier.height(40.dp))
    }
}

@Composable
private fun SubmitButton(
    isVisible: Boolean,
    isShowDelete: Boolean,
    onEvent: (EditWallPaperInfoScreenEvent) -> Unit = {}
) {
    if (isVisible) {
        Row(modifier = Modifier.fillMaxWidth(), horizontalArrangement = Arrangement.End) {

            if (isShowDelete) {
                val showDialog = remember {
                    mutableStateOf(false)
                }
                Button(onClick = {
                    showDialog.value = true
                }, modifier = Modifier.padding(10.dp)) {
                    Text(text = "删除", color = Color.White, fontSize = 20.dp2sp())
                }
                if (showDialog.value) {
                    TipDialog(title = "提示", content = "确定删除该壁纸?", confirmClick = {
                        onEvent(EditWallPaperInfoScreenEvent.Delete)
                        showDialog.value = false
                    }, onDismissRequest = {
                        showDialog.value = false
                    })
                }
            }
            Button(onClick = {
                onEvent(EditWallPaperInfoScreenEvent.Save)
            }, modifier = Modifier.padding(10.dp)) {
                Text(text = "保存", color = Color.White, fontSize = 20.dp2sp())
            }

        }

    }
}

@Composable
fun SelectTimeBox(timeFrame: TimeFrameState) {
    Column {
        Text(
            modifier = Modifier.padding(10.dp),
            text = "设置的时间段:",
            fontSize = 16.dp2sp(),
            color = Color.Black,
            textAlign = TextAlign.Center
        )
        Row {
            SelectText(
                modifier = Modifier
                    .width(100.dp)
                    .height(50.dp)
                    .padding(10.dp)
                    .clickableSafe {
                        timeFrame.antTimeFrame.value = true
                    }, text = "整天", isSelect = timeFrame.antTimeFrame.value
            )
            SelectText(
                modifier = Modifier
                    .width(100.dp)
                    .height(50.dp)
                    .padding(10.dp)
                    .clickableSafe {
                        timeFrame.antTimeFrame.value = false
                    }, text = "自定义", isSelect = !timeFrame.antTimeFrame.value
            )
        }

        if (!timeFrame.antTimeFrame.value) {
            Row {
                Text(modifier = Modifier.align(Alignment.CenterVertically), text = "开始时间:")
                EditTime(timeFrame.startTime)
            }
            Row {
                Text(modifier = Modifier.align(Alignment.CenterVertically), text = "结束时间:")
                EditTime(timeFrame.endTime)
            }
        }
    }
}

@OptIn(ExperimentalMaterial3Api::class)
@Composable
private fun EditTime(state: MutableState<EditWallPaperInfoTimeState>) {
    Row() {

        TextField(
            modifier = Modifier.width(100.dp),
            value = state.value.hour.toString(),
            onValueChange = { string ->
                tryCatch {
                    val newString = string.filter { char -> char.isDigit() }.let {
                        if (it.length > 2) {
                            it.substring(0, 2)
                        } else it
                    }
                    if (newString.isEmpty()) {
                        state.update { it.copy(hour = 0) }
                    } else {
                        state.update { it.copy(hour = newString.toInt()) }
                    }
                }

            },
            maxLines = 1,
            keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number)
        )
        Text(modifier = Modifier.align(Alignment.CenterVertically), text = ":")
        TextField(
            modifier = Modifier.width(100.dp),
            value = state.value.minute.toString(),
            onValueChange = {
                if (it.length <= 2) {
                    try {
                        val newString = it.filter { char -> char.isDigit() }
                        if (newString.isEmpty()) {
                            state.update { it.copy(minute = 0) }
                        } else {
                            state.update { it.copy(minute = newString.toInt()) }
                        }
                    } catch (e: Throwable) {

                    }
                }
            },
            maxLines = 1,
            keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number)
        )
    }
}

@Composable
private fun SelectWeekBox(week: EditWallPaperInfoWeekState) {
    Column {
        Text(
            modifier = Modifier.padding(10.dp),
            text = "设置的日期:",
            fontSize = 16.dp2sp(),
            color = Color.Black,
            textAlign = TextAlign.Center
        )
        Row {
            SelectText(
                modifier = Modifier
                    .width(100.dp)
                    .height(50.dp)
                    .padding(10.dp)
                    .clickableSafe {
                        week.anyDay.value = true
                    }, text = "每天", isSelect = week.anyDay.value
            )
            SelectText(
                modifier = Modifier
                    .width(100.dp)
                    .height(50.dp)
                    .padding(10.dp)
                    .clickableSafe {
                        week.anyDay.value = false
                    }, text = "自定义", isSelect = !week.anyDay.value
            )
        }
        if (!week.anyDay.value) {
            FlowRow {
                week.weekTips.forEachIndexed() { index, s ->
                    val isSelect = week.weekDayList.contains(index)
                    SelectText(
                        modifier = Modifier
                            .width(100.dp)
                            .height(50.dp)
                            .padding(10.dp)
                            .clickableSafe {
                                if (isSelect) {
                                    week.weekDayList.remove(index)
                                } else {
                                    week.weekDayList.add(index)
                                }
                            }, text = s, isSelect = isSelect
                    )
                }
            }
        }

    }
}

@Composable
private fun ForceShowSelectBox(state: MutableState<Boolean>) {
    Column {
        Text(
            modifier = Modifier.padding(10.dp),
            text = "是否强制展示:",
            fontSize = 16.dp2sp(),
            color = Color.Black,
            textAlign = TextAlign.Center
        )
        Row(modifier = Modifier.fillMaxWidth()) {
            SelectText(
                modifier = Modifier
                    .width(100.dp)
                    .height(50.dp)
                    .padding(10.dp)
                    .clickableSafe {
                        state.value = true
                    }, text = "强制展示", isSelect = state.value
            )
            SelectText(
                modifier = Modifier
                    .width(100.dp)
                    .height(50.dp)
                    .padding(10.dp)
                    .clickableSafe {
                        state.value = false
                    }, text = "随机展示", isSelect = !state.value
            )
        }
    }
}

@Composable
 fun SelectText(modifier: Modifier = Modifier, text: String, isSelect: Boolean) {
    val color = if (isSelect) colorMain else Color.Black
    Box(modifier = modifier.border(width = 1.dp, color = color, shape = RoundedCornerShape(6.dp)))
    {
        Text(
            modifier = Modifier.align(Alignment.Center),
            fontSize = 16.dp2sp(),
            text = text,
            color = color,
            textAlign = TextAlign.Center
        )
    }
}

@Composable
private fun ImageShow(uri: String, filePath: String, uriCall: (String) -> Unit) {
    val rememberLauncherForActivityResult =
        rememberLauncherForActivityResult(
            contract = getImageActivityResultContract(),
            onResult = {
                if (it != null) {
                    uriCall(it.toString())
                }
            })
    Box(modifier = Modifier
        .fillMaxWidth()
        .heightIn(min = 200.dp)
        .padding(10.dp)
        .onClickSafe() {
            rememberLauncherForActivityResult.launch(true)
        }) {

        if (uri.isEmpty() && filePath.isEmpty()) {
            Text(
                modifier = Modifier.align(Alignment.Center),
                text = "点击选择图片",
                fontSize = 16.dp2sp()
            )
        } else {
            val painter = if (uri.isNotEmpty()) {
                rememberUriPainterSafe(Uri.parse(uri))
            } else {
                rememberFilePainterSafe(filePath = filePath)
            }
            Image(
                modifier = Modifier
                    .align(Alignment.Center)
                    .clip(shape = RoundedCornerShape(10.dp)),
                painter = painter,
                contentDescription = ""
            )
        }
    }

}

